{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 准备工作\n",
    "\n",
    "1.确保您按照[README](README-CN.md)中的说明在环境中设置了API密钥\n",
    "\n",
    "2.安装依赖包"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "scrolled": true,
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.768389Z",
     "start_time": "2024-05-13T03:00:13.017619Z"
    }
   },
   "source": [
    "!pip install tiktoken openai pandas matplotlib plotly scikit-learn numpy"
   ],
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Requirement already satisfied: tiktoken in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (0.6.0)\n",
      "Requirement already satisfied: openai in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (1.20.0)\n",
      "Requirement already satisfied: pandas in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (2.2.2)\n",
      "Requirement already satisfied: matplotlib in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (3.8.4)\n",
      "Requirement already satisfied: plotly in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (5.22.0)\n",
      "Requirement already satisfied: scikit-learn in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (1.4.2)\n",
      "Requirement already satisfied: numpy in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (1.26.4)\n",
      "Requirement already satisfied: regex>=2022.1.18 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from tiktoken) (2023.12.25)\n",
      "Requirement already satisfied: requests>=2.26.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from tiktoken) (2.31.0)\n",
      "Requirement already satisfied: anyio<5,>=3.5.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (4.0.0)\n",
      "Requirement already satisfied: distro<2,>=1.7.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (1.9.0)\n",
      "Requirement already satisfied: httpx<1,>=0.23.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (0.25.1)\n",
      "Requirement already satisfied: pydantic<3,>=1.9.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (2.7.1)\n",
      "Requirement already satisfied: sniffio in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (1.3.0)\n",
      "Requirement already satisfied: tqdm>4 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (4.66.2)\n",
      "Requirement already satisfied: typing-extensions<5,>=4.7 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from openai) (4.9.0)\n",
      "Requirement already satisfied: python-dateutil>=2.8.2 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from pandas) (2.8.2)\n",
      "Requirement already satisfied: pytz>=2020.1 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from pandas) (2024.1)\n",
      "Requirement already satisfied: tzdata>=2022.7 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from pandas) (2024.1)\n",
      "Requirement already satisfied: contourpy>=1.0.1 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (1.2.1)\n",
      "Requirement already satisfied: cycler>=0.10 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (0.12.1)\n",
      "Requirement already satisfied: fonttools>=4.22.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (4.51.0)\n",
      "Requirement already satisfied: kiwisolver>=1.3.1 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (1.4.5)\n",
      "Requirement already satisfied: packaging>=20.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (23.2)\n",
      "Requirement already satisfied: pillow>=8 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (10.1.0)\n",
      "Requirement already satisfied: pyparsing>=2.3.1 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (3.1.1)\n",
      "Requirement already satisfied: importlib-resources>=3.2.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from matplotlib) (6.4.0)\n",
      "Requirement already satisfied: tenacity>=6.2.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from plotly) (8.2.3)\n",
      "Requirement already satisfied: scipy>=1.6.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from scikit-learn) (1.13.0)\n",
      "Requirement already satisfied: joblib>=1.2.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from scikit-learn) (1.3.2)\n",
      "Requirement already satisfied: threadpoolctl>=2.0.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from scikit-learn) (3.4.0)\n",
      "Requirement already satisfied: idna>=2.8 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from anyio<5,>=3.5.0->openai) (3.6)\n",
      "Requirement already satisfied: exceptiongroup>=1.0.2 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from anyio<5,>=3.5.0->openai) (1.1.3)\n",
      "Requirement already satisfied: certifi in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from httpx<1,>=0.23.0->openai) (2024.2.2)\n",
      "Requirement already satisfied: httpcore in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from httpx<1,>=0.23.0->openai) (1.0.2)\n",
      "Requirement already satisfied: zipp>=3.1.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from importlib-resources>=3.2.0->matplotlib) (3.18.1)\n",
      "Requirement already satisfied: annotated-types>=0.4.0 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from pydantic<3,>=1.9.0->openai) (0.6.0)\n",
      "Requirement already satisfied: pydantic-core==2.18.2 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from pydantic<3,>=1.9.0->openai) (2.18.2)\n",
      "Requirement already satisfied: six>=1.5 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from python-dateutil>=2.8.2->pandas) (1.16.0)\n",
      "Requirement already satisfied: charset-normalizer<4,>=2 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from requests>=2.26.0->tiktoken) (3.3.2)\n",
      "Requirement already satisfied: urllib3<3,>=1.21.1 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from requests>=2.26.0->tiktoken) (1.26.18)\n",
      "Requirement already satisfied: colorama in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from tqdm>4->openai) (0.4.6)\n",
      "Requirement already satisfied: h11<0.15,>=0.13 in d:\\programfiles\\miniconda\\envs\\allinone\\lib\\site-packages (from httpcore->httpx<1,>=0.23.0->openai) (0.14.0)\n"
     ]
    }
   ],
   "execution_count": 22
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.784319Z",
     "start_time": "2024-05-13T03:00:17.770356Z"
    }
   },
   "source": [],
   "outputs": [],
   "execution_count": 22
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 1. 生成 Embedding (基于 text-embedding-ada-002 模型)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "嵌入对于处理自然语言和代码非常有用，因为其他机器学习模型和算法（如聚类或搜索）可以轻松地使用和比较它们。"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": "![Embedding](images/embedding-vectors.svg)"
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### 亚马逊美食评论数据集(amazon-fine-food-reviews)\n",
    "\n",
    "Source:[美食评论数据集](https://www.kaggle.com/snap/amazon-fine-food-reviews)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "![dataset](images/amazon-fine-food-reviews.png)\n",
    "\n",
    "\n",
    "该数据集包含截至2012年10月用户在亚马逊上留下的共计568,454条美食评论。为了说明目的，我们将使用该数据集的一个子集，其中包括最近1,000条评论。这些评论都是用英语撰写的，并且倾向于积极或消极。每个评论都有一个产品ID、用户ID、评分、标题（摘要）和正文。\n",
    "\n",
    "我们将把评论摘要和正文合并成一个单一的组合文本。模型将对这个组合文本进行编码，并输出一个单一的向量嵌入。"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.800275Z",
     "start_time": "2024-05-13T03:00:17.786312Z"
    }
   },
   "source": [
    "# 导入 pandas 包。Pandas 是一个用于数据处理和分析的 Python 库\n",
    "# 提供了 DataFrame 数据结构，方便进行数据的读取、处理、分析等操作。\n",
    "import pandas as pd\n",
    "# 导入 tiktoken 库。Tiktoken 是 OpenAI 开发的一个库，用于从模型生成的文本中计算 token 数量。\n",
    "import tiktoken"
   ],
   "outputs": [],
   "execution_count": 23
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.816267Z",
     "start_time": "2024-05-13T03:00:17.802269Z"
    }
   },
   "source": [],
   "outputs": [],
   "execution_count": 23
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "#### 加载数据集"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.848155Z",
     "start_time": "2024-05-13T03:00:17.818229Z"
    }
   },
   "source": [
    "input_datapath = \"data/fine_food_reviews_1k.csv\"\n",
    "df = pd.read_csv(input_datapath, index_col=0)\n",
    "df = df[[\"Time\", \"ProductId\", \"UserId\", \"Score\", \"Summary\", \"Text\"]]\n",
    "df = df.dropna()\n",
    "\n",
    "# 将 \"Summary\" 和 \"Text\" 字段组合成新的字段 \"combined\"\n",
    "df[\"combined\"] = (\n",
    "    \"Title: \" + df.Summary.str.strip() + \"; Content: \" + df.Text.str.strip()\n",
    ")\n",
    "df.head(2)"
   ],
   "outputs": [
    {
     "data": {
      "text/plain": [
       "         Time   ProductId          UserId  Score  \\\n",
       "0  1351123200  B003XPF9BO  A3R7JR3FMEBXQB      5   \n",
       "1  1351123200  B003JK537S  A3JBPC3WFUT5ZP      1   \n",
       "\n",
       "                                             Summary  \\\n",
       "0  where does one  start...and stop... with a tre...   \n",
       "1                                  Arrived in pieces   \n",
       "\n",
       "                                                Text  \\\n",
       "0  Wanted to save some to bring to my Chicago fam...   \n",
       "1  Not pleased at all. When I opened the box, mos...   \n",
       "\n",
       "                                            combined  \n",
       "0  Title: where does one  start...and stop... wit...  \n",
       "1  Title: Arrived in pieces; Content: Not pleased...  "
      ],
      "text/html": [
       "<div>\n",
       "<style scoped>\n",
       "    .dataframe tbody tr th:only-of-type {\n",
       "        vertical-align: middle;\n",
       "    }\n",
       "\n",
       "    .dataframe tbody tr th {\n",
       "        vertical-align: top;\n",
       "    }\n",
       "\n",
       "    .dataframe thead th {\n",
       "        text-align: right;\n",
       "    }\n",
       "</style>\n",
       "<table border=\"1\" class=\"dataframe\">\n",
       "  <thead>\n",
       "    <tr style=\"text-align: right;\">\n",
       "      <th></th>\n",
       "      <th>Time</th>\n",
       "      <th>ProductId</th>\n",
       "      <th>UserId</th>\n",
       "      <th>Score</th>\n",
       "      <th>Summary</th>\n",
       "      <th>Text</th>\n",
       "      <th>combined</th>\n",
       "    </tr>\n",
       "  </thead>\n",
       "  <tbody>\n",
       "    <tr>\n",
       "      <th>0</th>\n",
       "      <td>1351123200</td>\n",
       "      <td>B003XPF9BO</td>\n",
       "      <td>A3R7JR3FMEBXQB</td>\n",
       "      <td>5</td>\n",
       "      <td>where does one  start...and stop... with a tre...</td>\n",
       "      <td>Wanted to save some to bring to my Chicago fam...</td>\n",
       "      <td>Title: where does one  start...and stop... wit...</td>\n",
       "    </tr>\n",
       "    <tr>\n",
       "      <th>1</th>\n",
       "      <td>1351123200</td>\n",
       "      <td>B003JK537S</td>\n",
       "      <td>A3JBPC3WFUT5ZP</td>\n",
       "      <td>1</td>\n",
       "      <td>Arrived in pieces</td>\n",
       "      <td>Not pleased at all. When I opened the box, mos...</td>\n",
       "      <td>Title: Arrived in pieces; Content: Not pleased...</td>\n",
       "    </tr>\n",
       "  </tbody>\n",
       "</table>\n",
       "</div>"
      ]
     },
     "execution_count": 24,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "execution_count": 24
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.864112Z",
     "start_time": "2024-05-13T03:00:17.849154Z"
    }
   },
   "source": [
    "df[\"combined\"]"
   ],
   "outputs": [
    {
     "data": {
      "text/plain": [
       "0      Title: where does one  start...and stop... wit...\n",
       "1      Title: Arrived in pieces; Content: Not pleased...\n",
       "2      Title: It isn't blanc mange, but isn't bad . ....\n",
       "3      Title: These also have SALT and it's not sea s...\n",
       "4      Title: Happy with the product; Content: My dog...\n",
       "                             ...                        \n",
       "995    Title: Delicious!; Content: I have ordered the...\n",
       "996    Title: Good Training Treat; Content: My dog wi...\n",
       "997    Title: Jamica Me Crazy Coffee; Content: Wolfga...\n",
       "998    Title: Party Peanuts; Content: Great product f...\n",
       "999    Title: I love Maui Coffee!; Content: My first ...\n",
       "Name: combined, Length: 1000, dtype: object"
      ]
     },
     "execution_count": 25,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "execution_count": 25
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.880099Z",
     "start_time": "2024-05-13T03:00:17.866106Z"
    }
   },
   "source": [],
   "outputs": [],
   "execution_count": 25
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "#### Embedding 模型关键参数"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.896026Z",
     "start_time": "2024-05-13T03:00:17.882064Z"
    }
   },
   "source": [
    "# 模型类型\n",
    "# 建议使用官方推荐的第二代嵌入模型：text-embedding-ada-002\n",
    "embedding_model = \"text-embedding-ada-002\"\n",
    "# text-embedding-ada-002 模型对应的分词器（TOKENIZER）\n",
    "embedding_encoding = \"cl100k_base\"\n",
    "# text-embedding-ada-002 模型支持的输入最大 Token 数是8191，向量维度 1536\n",
    "# 在我们的 DEMO 中过滤 Token 超过 8000 的文本\n",
    "max_tokens = 8000  "
   ],
   "outputs": [],
   "execution_count": 26
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "#### 将样本减少到最近的1,000个评论，并删除过长的样本\n"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:17.987782Z",
     "start_time": "2024-05-13T03:00:17.897025Z"
    }
   },
   "source": [
    "# 设置要筛选的评论数量为1000\n",
    "top_n = 1000\n",
    "# 对DataFrame进行排序，基于\"Time\"列，然后选取最后的2000条评论。\n",
    "# 这个假设是，我们认为最近的评论可能更相关，因此我们将对它们进行初始筛选。\n",
    "df = df.sort_values(\"Time\").tail(top_n * 2) \n",
    "# 丢弃\"Time\"列，因为我们在这个分析中不再需要它。\n",
    "df.drop(\"Time\", axis=1, inplace=True)\n",
    "# 从'embedding_encoding'获取编码\n",
    "encoding = tiktoken.get_encoding(embedding_encoding)\n",
    "\n",
    "# 计算每条评论的token数量。我们通过使用encoding.encode方法获取每条评论的token数，然后把结果存储在新的'n_tokens'列中。\n",
    "df[\"n_tokens\"] = df.combined.apply(lambda x: len(encoding.encode(x)))\n",
    "\n",
    "# 如果评论的token数量超过最大允许的token数量，我们将忽略（删除）该评论。\n",
    "# 我们使用.tail方法获取token数量在允许范围内的最后top_n（1000）条评论。\n",
    "df = df[df.n_tokens <= max_tokens].tail(top_n)\n",
    "\n",
    "# 打印出剩余评论的数量。\n",
    "len(df)"
   ],
   "outputs": [
    {
     "data": {
      "text/plain": [
       "1000"
      ]
     },
     "execution_count": 27,
     "metadata": {},
     "output_type": "execute_result"
    }
   ],
   "execution_count": 27
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "#### 生成 Embeddings 并保存\n"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:18.003740Z",
     "start_time": "2024-05-13T03:00:17.989777Z"
    }
   },
   "source": [
    "from openai import OpenAI\n",
    "import os"
   ],
   "outputs": [],
   "execution_count": 28
  },
  {
   "cell_type": "code",
   "metadata": {
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:18.865474Z",
     "start_time": "2024-05-13T03:00:18.005735Z"
    }
   },
   "source": [
    "# OpenAI Python SDK v1.0 更新后的使用方式\n",
    "# 使用网龙自己的URL\n",
    "client = OpenAI(base_url=\"https://bd-gateway-agent.sdpsg.101.com/openai/v1/\", api_key=os.getenv(\"OPENAI_API_KEY\"))"
   ],
   "outputs": [],
   "execution_count": 29
  },
  {
   "cell_type": "code",
   "metadata": {
    "scrolled": true,
    "ExecuteTime": {
     "end_time": "2024-05-13T03:00:23.409398Z",
     "start_time": "2024-05-13T03:00:23.066275Z"
    }
   },
   "source": [
    "# 新版本创建 Embedding 向量的方法\n",
    "# Ref：https://community.openai.com/t/embeddings-api-documentation-needs-to-updated/475663\n",
    "res = client.embeddings.create(input=\"这是一段有待embedding的文本\", model=embedding_model)\n",
    "print(res.data[0].embedding)"
   ],
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "[-0.02102220058441162, -0.013249342329800129, -0.0028604252729564905, -0.00404376070946455, -0.0065409839153289795, 0.0015390057815238833, -0.011200682260096073, -0.00439859414473176, -0.036661647260189056, -0.015826905146241188, -0.0072372606955468655, 0.03170736879110336, -0.003508163383230567, -0.005058048292994499, 0.01259323488920927, 0.02327170968055725, 0.021209659054875374, 0.007538534235209227, 0.010926187969744205, -0.01909404993057251, -0.008355320431292057, 0.007491669617593288, 0.0011289389804005623, 0.000875367084518075, -0.020888300612568855, 0.0013825109926983714, 0.025909526273608208, -0.033635519444942474, -0.007411330007016659, -0.015157408080995083, 0.019535917788743973, -0.02601664699614048, -0.01121407188475132, -0.024704432114958763, 0.004114057868719101, -0.00754522904753685, -0.015947414562106133, -0.023298488929867744, 0.023660017177462578, -0.017112338915467262, 0.019107438623905182, 0.006581153720617294, 0.01792912557721138, 0.011488565243780613, -0.008047351613640785, -0.0036822324618697166, 0.00025984845706261694, -0.008027266710996628, -0.014742320403456688, 0.018625400960445404, 0.030743293464183807, 0.012024163268506527, -0.026900382712483406, -0.025039181113243103, 0.0022578779608011246, 0.018210314214229584, -0.012566455639898777, 0.009687619283795357, -0.0031734148506075144, -0.014876219443976879, 0.0035650706849992275, 0.018732521682977676, -0.019147608429193497, -0.00133313552942127, -0.02293696068227291, -0.00787328276783228, -0.014822660014033318, 0.0009791391203179955, 0.017888955771923065, 0.020741011947393417, 0.03877725452184677, 0.016724031418561935, -0.0038931239396333694, -0.004991098772734404, 0.04571324214339256, -0.008408879861235619, -0.013430106453597546, -0.007973707281053066, 0.006875732447952032, 0.0007138510118238628, 0.012506200931966305, -0.02300391159951687, 0.008321845903992653, 0.02242814376950264, 0.000867835246026516, 0.0022980477660894394, -0.018719131126999855, 0.034813836216926575, -0.03160025179386139, -0.016657080501317978, 0.0023817350156605244, 0.019134219735860825, 0.0014210069784894586, 0.02343238890171051, 0.011281021870672703, 0.048659030348062515, -0.010183046571910381, 0.02617732621729374, 0.021223049610853195, -0.026913773268461227, 0.01743369735777378, 0.0035416381433606148, -0.028654463589191437, -0.008000487461686134, -0.048418011516332626, -0.0050613959319889545, 0.01625538244843483, -0.010162961669266224, 0.030314816161990166, 0.02084813080728054, -0.025226639583706856, 0.01526452787220478, -0.013430106453597546, -0.021905936300754547, -0.009372955188155174, -0.0015205946983769536, 0.024168835952878, -0.02902938239276409, -0.01550554670393467, -0.0126735744997859, 0.000766992277931422, 0.04549900442361832, 0.007906757295131683, -0.008676678873598576, 0.008984647691249847, -0.0016611890168860555, 0.004314906895160675, -0.008000487461686134, -0.0060422089882195, -0.008542779833078384, 0.024195615202188492, 0.007431414909660816, 0.026378175243735313, 0.010357115417718887, -0.032216187566518784, 0.029645320028066635, -0.012867729179561138, -0.003019430674612522, -0.028225986286997795, -0.01693826913833618, 0.01176305953413248, 0.017487257719039917, -0.02060711197555065, -0.021986275911331177, 0.014112993143498898, -0.006587848532944918, -0.014112993143498898, 0.003983506001532078, 0.00533254211768508, -0.006782002747058868, 0.018973540514707565, -0.005198643077164888, 0.010644999332726002, 0.010350421071052551, -0.012934678234159946, 0.02667275443673134, 0.0038629965856671333, -0.0014009220758453012, -0.012071027420461178, 0.003004366997629404, 0.01926811784505844, 0.012352216057479382, 0.013651040382683277, 0.0019398670410737395, 0.004840462002903223, 0.030475495383143425, 0.00125530653167516, -0.0013691210187971592, 0.015813514590263367, -0.0022930265404284, -0.016308942809700966, 0.017714885994791985, -0.014313842169940472, 0.005680680740624666, -0.016549961641430855, 0.027061061933636665, 0.011495260521769524, 0.01292798388749361, -0.008161166682839394, -0.023244930431246758, -0.03360874205827713, -0.0034345188178122044, 0.009004732593894005, 0.00942651554942131, -0.014902999624609947, -0.007605483755469322, 0.006949377246201038, -0.012613319791853428, -0.005108260549604893, -0.005710808094590902, 0.020901691168546677, 0.02684682235121727, -0.00045191036770120263, -0.012887814082205296, -0.632004976272583, -0.003385980147868395, 0.02509274147450924, -0.012861033901572227, 0.017540816217660904, 0.02375374734401703, 0.004545883275568485, -0.00017501066031400114, -0.018960149958729744, -0.03226974606513977, -0.01975015550851822, -0.013329681940376759, -0.0006795392837375402, -0.011890263296663761, -0.005590298678725958, 0.003755877260118723, 0.003012735629454255, -0.029243621975183487, 0.00692259706556797, 0.005734240170568228, -0.0037893520202487707, 0.014287061989307404, -0.006597890984266996, 0.012526285834610462, 0.0024503583554178476, 0.01329620648175478, -0.007163615897297859, -0.008703459054231644, -0.009399735368788242, 0.03577791154384613, -0.03366230055689812, 0.0204196535050869, -0.008777103386819363, -0.002766695572063327, 0.05500585958361626, -0.018304042518138885, -0.0070029366761446, 0.0004119497607462108, 0.022200515493750572, 0.017875565215945244, -0.015559106133878231, -0.01526452787220478, 0.007471584714949131, -0.017955904826521873, 0.003059600479900837, 0.005901614669710398, 0.03034159541130066, -0.0040906257927417755, 0.008208030834794044, 0.02977921813726425, -0.0023131114430725574, 0.022146955132484436, 0.011341276578605175, -0.012653489597141743, -0.020245583727955818, -0.01767471618950367, 0.019027099013328552, -0.05128345638513565, 0.005479831714183092, 0.011769753880798817, 0.002316459082067013, 0.02017863467335701, -0.004053803160786629, -0.00638030469417572, -0.02017863467335701, 0.007458194624632597, -0.03893793374300003, 0.018330823630094528, 0.01708555966615677, -0.0009481748566031456, 0.0054028392769396305, 0.012091112323105335, -0.01371129509061575, -0.01329620648175478, 0.012486116029322147, 0.0374918207526207, 0.00588152976706624, -0.020794572308659554, -0.0075920941308140755, 0.015545716509222984, 0.010323640890419483, -0.015947414562106133, -0.011060087941586971, 0.0015699700452387333, -0.0016812739195302129, 0.0010251670610159636, -0.04228542000055313, 0.006534289103001356, 0.02493206225335598, -0.008027266710996628, 0.0054865265265107155, -0.0035885029938071966, -0.008823968470096588, -0.01338324137032032, -0.004934191703796387, 0.0160813145339489, -0.0007778716390021145, 0.003215258475393057, 0.022736111655831337, 0.0024721170775592327, 0.01259323488920927, 0.01121407188475132, -0.004187702666968107, -0.00950015988200903, 0.0177550558000803, -0.008141081780195236, -0.010029062628746033, -0.008971257135272026, 0.015492156147956848, -0.02250848338007927, -0.021731866523623466, -0.01958947628736496, 0.006544331554323435, -0.011167206801474094, -0.026311224326491356, -0.02777072787284851, -0.0015674594324082136, 0.0034947735257446766, -0.0007402124465443194, 0.025574779137969017, 0.011615769937634468, 0.023244930431246758, 0.014983339235186577, 0.011555515229701996, 0.01221162173897028, 0.014943169429898262, -0.009185496717691422, -0.048337671905756, -0.010075926780700684, -0.005871487315744162, -0.019040489569306374, -0.005978606641292572, 0.045740023255348206, -0.030796853825449944, 0.021289998665452003, -0.009272530674934387, 0.007980402559041977, -0.012606625445187092, 0.013503750786185265, -0.027302080765366554, -0.003755877260118723, 0.019576087594032288, 0.01810319349169731, -0.015358257107436657, -0.018143363296985626, -0.004147532861679792, -0.020714230835437775, -0.005058048292994499, -0.010156266391277313, -0.0022277506068348885, 0.004927496425807476, 0.0019532570149749517, -0.0055869510397315025, 0.013898754492402077, 0.008542779833078384, 0.020580332726240158, 0.00023641606094315648, -0.01792912557721138, -0.012312046252191067, 0.003548333188518882, -0.021718477830290794, 0.0005770225543528795, -0.022829841822385788, -0.007940232753753662, -0.015492156147956848, -0.007565313950181007, -0.00871684867888689, 0.009520244784653187, -0.028333105146884918, -0.027636829763650894, -0.009908553212881088, 0.005901614669710398, -0.012613319791853428, -0.003474688623100519, -0.006490771658718586, -0.0073242951184511185, -0.022736111655831337, -0.01567961648106575, -0.0020453128963708878, -0.022870011627674103, 0.009399735368788242, -0.00933948066085577, -0.0040939729660749435, -0.00850261002779007, -0.0005146756884641945, 0.01205094251781702, 0.014648590236902237, 0.015599275939166546, -0.013791634701192379, 0.00462957052513957, 0.009292615577578545, 0.019040489569306374, -0.02726191096007824, 0.018652182072401047, 0.025815797969698906, 0.02577562816441059, -0.021544408053159714, 0.020714230835437775, 0.010303555987775326, 0.009152021259069443, 0.02008490450680256, 0.005884876940399408, -0.017219457775354385, -0.005831317510455847, 0.00735777011141181, -0.02434290386736393, -0.017246238887310028, 0.0003711523022502661, 0.014782490208745003, 0.007752773351967335, 0.009788043797016144, 0.0019147609127685428, -0.015291307121515274, 0.0010360463056713343, -0.01683115027844906, 0.03133245185017586, -0.02400815673172474, 0.009640754200518131, -0.0010477625764906406, 0.006976156961172819, -0.016362503170967102, -0.01983049511909485, 0.009285921230912209, -0.011187291704118252, -0.010296860709786415, -0.006360219791531563, 0.009031511843204498, 0.028145646676421165, 0.01246603112667799, -0.01492977887392044, -0.019709985703229904, 0.007565313950181007, 0.007839808240532875, 0.026913773268461227, -0.004301517270505428, -0.023914426565170288, 0.041642703115940094, -0.015291307121515274, 0.0388575941324234, 0.004097320605069399, 0.005797842517495155, 0.020633891224861145, 0.022481704130768776, -0.017701495438814163, 0.008542779833078384, 0.010745423845946789, 0.04710579663515091, 0.0161750428378582, -0.012539675459265709, 0.01909404993057251, -0.02967209927737713, 0.021865766495466232, -0.019375238567590714, 0.008536084555089474, 0.03133245185017586, -0.024195615202188492, 0.0024737906642258167, 0.028574123978614807, 0.021624747663736343, 0.02383408695459366, 0.0028085391968488693, 0.004592748358845711, 0.00429147481918335, 0.022481704130768776, 0.009111851453781128, -0.006125895772129297, -0.007705908268690109, -0.01417994312942028, -0.008462440222501755, -0.0011029960587620735, 0.0026746399234980345, -0.007853197865188122, 0.01130110677331686, -0.007973707281053066, 0.018330823630094528, -0.012238401919603348, 0.0247579924762249, -0.009131936356425285, -0.0006021286826580763, -0.0048036398366093636, -0.020620502531528473, -0.02852056547999382, 0.011803229339420795, 0.010959663428366184, -0.006326744798570871, -0.015960805118083954, -0.03170736879110336, 0.023566288873553276, -0.014621810987591743, 0.011394836008548737, 0.00912524200975895, -0.002726525766775012, 0.018330823630094528, -0.008395490236580372, 0.0014511343324556947, 0.023820696398615837, 0.025494439527392387, 0.0022930265404284, -0.034653156995773315, -0.0018260525539517403, 0.0011917043011635542, -0.007725993171334267, 0.011441701091825962, -0.01675081066787243, 0.031814489513635635, -0.019709985703229904, -0.0037357923574745655, 0.016697250306606293, -0.009547024965286255, -0.010845848359167576, -0.017326578497886658, 0.0074247196316719055, -0.008214726112782955, -0.02469104342162609, 0.0053994921036064625, 0.023298488929867744, -0.0005514980293810368, 0.000360063771950081, 0.03176093101501465, 0.003725749906152487, 0.0034110862761735916, -0.015880465507507324, -0.02242814376950264, 0.026297835633158684, 0.012057637795805931, 0.029377520084381104, -0.0032186058815568686, 0.004622875712811947, 0.011789838783442974, -0.004729995038360357, -0.03192161023616791, -0.008020572364330292, 0.012238401919603348, -0.002370018744841218, 0.0003431171353440732, -0.0065275938250124454, 0.0074381097219884396, 0.013604175299406052, 0.025132911279797554, 0.00020430113363545388, -0.0026528812013566494, -0.0010870954720303416, 0.0032872294541448355, -0.02558816783130169, -0.002935743657872081, 0.01042406540364027, 0.013597480952739716, 0.0026612498331815004, -0.008120996877551079, -0.034144338220357895, 0.012486116029322147, 0.02817242592573166, 0.000422201439505443, -0.019482357427477837, 0.0017758402973413467, -0.0015841968124732375, -0.00809421669691801, 0.002150758635252714, -0.022816451266407967, 0.014046043157577515, -0.0025306979659944773, 0.02201305516064167, 0.016724031418561935, 0.01333637721836567, 0.00475342757999897, 0.043490514159202576, 0.015867074951529503, 0.004756774753332138, 0.021062370389699936, -0.026753094047307968, -0.00568737555295229, 0.013035102747380733, -0.028868703171610832, -0.007310905493795872, 0.020794572308659554, 0.0005770225543528795, -0.01901371031999588, -0.01708555966615677, 0.014059433713555336, 0.009942027740180492, -0.012881118804216385, -0.0038596491795033216, 0.01859862171113491, -0.0026980722323060036, -0.00646064430475235, -0.029297180473804474, -0.005975259002298117, -0.02402154542505741, -0.01851828210055828, -0.0037525296211242676, -0.0031399400904774666, -0.01634911261498928, 0.006095768418163061, -0.00933948066085577, 0.0311717726290226, -0.015291307121515274, -0.011281021870672703, -0.03500129282474518, 0.012492810375988483, 0.004244609735906124, 0.015974193811416626, -0.011180597357451916, -0.011147121898829937, 0.004271389916539192, 0.004368466790765524, -0.0126735744997859, 0.0014737298479303718, -0.03746504336595535, 0.006135938223451376, 0.03002023696899414, -0.014019263908267021, -0.014621810987591743, -0.0010837479494512081, -0.013818414881825447, 0.03727758303284645, -0.002579236403107643, 0.018986929208040237, 0.004800292197614908, 0.019884055480360985, -0.005198643077164888, -0.0029474596958607435, 0.010611524805426598, 0.0009933658875524998, -0.031734149903059006, -0.007598788943141699, -0.03409077972173691, -0.001866222359240055, -0.005777757614850998, 0.0194287970662117, -0.005965216550976038, -0.00677196029573679, 0.027369029819965363, 0.014206722378730774, 0.0009875078685581684, 0.007920147851109505, -0.0037123598158359528, 0.004301517270505428, 0.0048036398366093636, 0.005831317510455847, 0.0017825353424996138, -0.005724197719246149, 0.026070205494761467, -0.010290166363120079, -0.015411816537380219, 0.01858523115515709, -0.017701495438814163, -0.0006381141720339656, 0.03170736879110336, -0.004465543664991856, 0.019361848011612892, -0.015023509040474892, -0.024396464228630066, -0.012372300960123539, -0.00413079559803009, 0.007920147851109505, 0.025989865884184837, -0.003772614523768425, -0.015518936328589916, -0.029082942754030228, -0.00502122612670064, -0.006102463696151972, -0.0014519712422043085, 0.004170965403318405, 0.0014067802112549543, -0.01983049511909485, -0.009285921230912209, 0.01409960351884365, -0.004659697879105806, 0.025802407413721085, -0.02993989735841751, -0.02135694958269596, 0.007016326766461134, 0.006852299906313419, 0.011830008588731289, 0.020138464868068695, 0.0017557553946971893, -0.00925244577229023, -0.006310007534921169, 5.570422945311293e-05, -0.02268255315721035, -0.01799607463181019, -0.005804537329822779, 0.014688760042190552, -0.002686355961486697, 0.051069218665361404, -0.01276060938835144, -0.010718644596636295, 0.02301730029284954, -0.002589278854429722, 0.018491502851247787, -0.016375891864299774, -0.017741665244102478, -0.004422026686370373, 0.0010276776738464832, 0.008857442997395992, 0.015867074951529503, -0.01197060290724039, -0.004967666231095791, -0.005764367524534464, 0.010551270097494125, -0.004770164843648672, 0.00588152976706624, -0.016857929527759552, -0.03320704400539398, -0.02017863467335701, 0.004080583341419697, -0.00421113520860672, 0.00800718180835247, -0.014889609068632126, -0.01893337070941925, 0.025494439527392387, -0.0048605469055473804, 0.02769038826227188, 0.003842911683022976, 0.0061158533208072186, -0.023044081404805183, -0.0016009343089535832, -0.012941373512148857, 0.00498440396040678, -0.010698559693992138, 0.0034211287274956703, -0.017822004854679108, 0.0048337671905756, 0.04472238942980766, 0.03925929218530655, 0.008850747719407082, -0.006835562642663717, -0.01017635129392147, 0.006614628713577986, 0.006949377246201038, -0.0016385935014113784, -0.015639446675777435, -0.0010586418211460114, -0.02118287980556488, -0.03052905574440956, -0.008991342037916183, -0.018946759402751923, -0.03826843947172165, 0.010310251265764236, 0.011689414270222187, -0.02585596777498722, 0.002739915857091546, -0.005854749586433172, -0.0091721061617136, -0.014996728859841824, 0.014461131766438484, 0.035054855048656464, -0.004830419551581144, 0.009131936356425285, 0.035885028541088104, -0.008696763776242733, -0.015987584367394447, -0.045070525258779526, 0.004147532861679792, -0.009018122218549252, 0.03762572258710861, 0.06486085057258606, 0.004539188463240862, 0.003175088670104742, 0.0002349515416426584, 0.003538290737196803, 0.009111851453781128, -0.028467005118727684, 0.01760776713490486, 0.001657841494306922, -0.010537880472838879, 0.002028575399890542, -0.014595030806958675, -0.032135847955942154, 0.008509304374456406, -0.029243621975183487, -0.0074247196316719055, -0.04391899332404137, -0.0096675343811512, -0.009299310855567455, 0.011441701091825962, -0.010524489916861057, 0.004930844064801931, -0.0020001218654215336, -0.011347970925271511, -0.012037552893161774, -0.00888422317802906, -0.01501011848449707, -0.0014611767837777734, 0.0004418679163791239, 0.03368908166885376, -0.001262838370166719, -0.018826249986886978, 0.015612665563821793, 0.01142831053584814, -0.013791634701192379, -0.009741178713738918, -0.018960149958729744, 0.03952709212899208, -0.007136836182326078, -0.013256036676466465, 0.011120342649519444, 0.012613319791853428, 0.021544408053159714, 0.022695941850543022, 0.007719298359006643, -0.005101565737277269, -0.010946272872388363, 0.005379407200962305, -0.007377855014055967, 0.005024573765695095, 0.00506474357098341, 0.004488976206630468, -0.0002439478994347155, 0.002247835509479046, -0.0009724441333673894, -0.02134355902671814, -0.02518646977841854, -0.017567597329616547, -0.02574884705245495, -0.009754568338394165, -0.003873039036989212, 0.020781181752681732, -0.007585398852825165, -0.006340134888887405, 0.01791573502123356, 0.04908750578761101, -0.01083915401250124, 0.013858584687113762, 0.008241506293416023, 0.010778899304568768, 0.005925046745687723, 0.001556580071337521, 0.02477138303220272, -0.013229257427155972, 0.03261788561940193, -0.020888300612568855, -0.007210480980575085, -0.006253100465983152, -0.023285100236535072, 0.00763226393610239, -0.0060422089882195, -0.005523348692804575, 0.004723300226032734, -0.006390347145497799, -0.002758326940238476, 0.006889122538268566, -0.022200515493750572, 0.015117238275706768, 0.0021708435378968716, 0.008375405333936214, 0.007458194624632597, -0.03717046231031418, 0.006869037635624409, 0.0016854582354426384, -0.0045358408242464066, -0.007284125313162804, -0.03818809986114502, -0.021718477830290794, 0.0026378175243735313, 0.012506200931966305, -0.013517141342163086, -0.02560155838727951, -0.03010057657957077, -0.01735335774719715, -0.027328860014677048, 0.019884055480360985, 0.0015130628598853946, 0.013055187650024891, 0.018277263268828392, 0.021464068442583084, -0.010229911655187607, -0.009942027740180492, 0.003943336196243763, -0.022066615521907806, -0.015907244756817818, -0.006109158508479595, -0.03500129282474518, -0.018705740571022034, -0.009399735368788242, 0.02769038826227188, 0.023057470098137856, -0.009821518324315548, -0.026485294103622437, 0.005834664683789015, -0.046061381697654724, -0.008100911974906921, -0.007605483755469322, 0.0035818079486489296, 0.015492156147956848, 0.014581641182303429, 0.012733829207718372, 0.015773344784975052, -0.01284764427691698, 0.01442096196115017, -0.020392872393131256, 0.00286544649861753, -0.004254652187228203, -0.024878501892089844, -0.005811232607811689, 0.018116584047675133, -0.028145646676421165, -0.0050613959319889545, 0.013262731954455376, 0.012814168818295002, -0.007752773351967335, 0.03711690381169319, 0.005901614669710398, -0.018129974603652954, -0.008951172232627869, 0.004810334648936987, -0.014621810987591743, -0.000890430761501193, 0.017045389860868454, -0.01593402400612831, -0.014273672364652157, -0.003352505387738347, 0.013396631926298141, -0.017380136996507645, 0.015813514590263367, -0.013530530966818333, -0.0008762039942666888, 0.015800125896930695, -0.006949377246201038, 0.004796944558620453, -0.0026127113960683346, -0.019723376259207726, 0.03141279146075249, -0.008114301599562168, -0.017741665244102478, 0.038991495966911316, 0.013195781968533993, -0.009393040090799332, -0.011890263296663761, 0.01766132563352585, -0.02560155838727951, -0.023070860654115677, 0.0140058733522892, -0.006132591050118208, -0.004023675806820393, -0.008315150626003742, 0.009131936356425285, 0.006166065577417612, -0.007223870605230331, 0.009131936356425285, -0.018156753852963448, -0.02483833208680153, 0.01042406540364027, 0.017781835049390793, -0.02384747751057148, -0.009439905174076557, -0.006969462148845196, -0.00912524200975895, -0.029297180473804474, -0.013015017844736576, 0.0047902497462928295, -0.016978438943624496, -0.0033943490125238895, 0.007371160201728344, -0.0013046819949522614, 0.0014176595723256469, -0.008482525125145912, -0.0007238934631459415, -0.010544574819505215, 0.005901614669710398, 0.2997203469276428, -0.033715859055519104, -0.0014444394037127495, 0.016041144728660583, 0.004057150799781084, 0.0009431536309421062, 0.01384519413113594, -0.0007682475843466818, -0.020955251529812813, 0.004385204054415226, 0.0074247196316719055, -0.005078133195638657, 0.011542125605046749, -0.01735335774719715, -0.003648757701739669, -0.025641728192567825, -0.016121484339237213, -0.017822004854679108, -0.023633237928152084, -0.04268711805343628, 0.010015672072768211, -0.00792684219777584, -0.00614932831376791, -0.036233168095350266, 0.010993137955665588, -0.021397119387984276, -0.009901857934892178, -0.02143728919327259, 0.010899408720433712, 0.04308881610631943, -0.022080006077885628, -0.0018846335588023067, 0.00517186289653182, 0.003074664156883955, -0.026230884715914726, 0.006822172552347183, 0.03770606219768524, 0.014126382768154144, 0.044990185648202896, 0.0171658992767334, 0.03583147004246712, -0.02191932685673237, -0.004010286182165146, -0.0002826531999744475, 0.001347362413071096, 0.016871320083737373, -0.009439905174076557, -0.007163615897297859, -0.02884192392230034, 0.01417994312942028, 0.0053994921036064625, 0.005908309482038021, 0.02191932685673237, 0.020874911919236183, -0.0031399400904774666, 0.00043266231659799814, 0.029564980417490005, 0.010986442677676678, -0.005807884968817234, 0.006721748039126396, 0.01657674089074135, 0.03446569666266441, -0.009064987301826477, 0.013778245076537132, 0.010370505973696709, 0.01851828210055828, -0.04043760895729065, -0.0010059189517050982, -0.02384747751057148, -0.017232848331332207, 0.0150904580950737, -0.005161820445209742, -0.008495914749801159, 0.0054865265265107155, -0.04611494019627571, -0.03109143301844597, 0.03285890445113182, 0.023164590820670128, 0.023285100236535072, 0.03141279146075249, -0.02033931389451027, -0.004097320605069399, 0.015157408080995083, -0.013564005494117737, -0.013912144117057323, -0.049971241503953934, 0.008529389277100563, -0.015144018456339836, -0.010310251265764236, -0.015036898665130138, 0.00210556760430336, 0.004482281394302845, -0.0025273505598306656, -0.00879718828946352, 0.0020101643167436123, 0.0048605469055473804, -0.003755877260118723, 0.029618538916110992, -0.0027164833154529333, -0.0010469256667420268, -0.03393010050058365, 0.02134355902671814, 0.0177550558000803, 0.008897612802684307, -0.01909404993057251, -0.006209583021700382, -0.005382754374295473, 0.004679782781749964, 0.009828213602304459, -0.013584090396761894, -0.0031031176913529634, -0.014112993143498898, 0.013979094102978706, -0.02075440250337124, -0.010189741849899292, -0.004324949346482754, 0.02116948924958706, -0.024570534005761147, 0.0009557066950947046, -0.010069232434034348, -0.010223216377198696, -0.027208350598812103, -0.01166932936757803, -0.006621323525905609, -0.005255550146102905, -0.016282163560390472, -0.016951659694314003, -0.006310007534921169, 0.017286408692598343, -0.02935074083507061, 0.022133564576506615, -0.012499505653977394, 0.016456231474876404, 0.007732688449323177, -0.0038395642768591642, 0.020647281780838966, 0.011200682260096073, 0.009707704186439514, 0.0038998189847916365, 0.015893854200839996, -0.0014042695984244347, -0.02951142005622387, 0.01059813518077135, 0.014327231794595718, 0.004770164843648672, -0.0023532812483608723, 0.020151853561401367, 0.006862342357635498, 0.033715859055519104, -0.006005386356264353, -0.03454603627324104, -0.009567109867930412, -0.0001421634660800919, -0.007612179033458233, 0.028386665508151054, -0.016616910696029663, -0.025481048971414566, -0.034653156995773315, -0.009038207121193409, 0.009366260841488838, -0.04303525760769844, -0.0027449370827525854, 0.026900382712483406, -0.03486739471554756, -0.0004544209805317223, -0.008904308080673218, -0.17289085686206818, 0.002184233395382762, 0.010491015389561653, -0.023552898317575455, 0.03267144411802292, 0.012566455639898777, 0.021999666467308998, 0.0076791285537183285, 0.0008661615429446101, -0.0010971379233524203, 0.025574779137969017, -0.030984312295913696, -0.03853623569011688, -0.010370505973696709, -0.01818353310227394, 0.020901691168546677, -0.03462637588381767, -0.014688760042190552, 0.01808980479836464, 0.002316459082067013, 0.02134355902671814, -0.028118867427110672, -0.0037056650035083294, -0.020232193171977997, -0.0029842820949852467, 0.013697905465960503, 0.011716194450855255, 0.011060087941586971, -0.007190396077930927, 0.01952252723276615, 0.010745423845946789, -0.009031511843204498, 0.029913118109107018, 0.005369364749640226, 0.017380136996507645, 0.009560414589941502, 0.024945450946688652, -0.007531839422881603, -0.014474521391093731, 0.01355061586946249, 0.026485294103622437, 0.0242625642567873, 0.003772614523768425, -0.00043015170376747847, 0.007223870605230331, 0.01709894835948944, 0.005884876940399408, -0.022829841822385788, 0.031198551878333092, 0.01333637721836567, 0.009486770257353783, -0.024222394451498985, 0.02544087916612625, 0.010444150306284428, 0.011488565243780613, 0.023070860654115677, -0.005653900559991598, 0.01941540837287903, 0.0018963497132062912, 0.03366230055689812, -0.0009088419610634446, -0.012144672684371471, -0.001348199206404388, -0.005878182128071785, -0.008033961988985538, -0.02201305516064167, -0.027382420375943184, 0.004733342677354813, 0.01363765075802803, 0.006835562642663717, -0.012091112323105335, -0.014300452545285225, 0.021035591140389442, 0.004385204054415226, 0.01835760287940502, 0.0006376957171596587, -0.033314161002635956, 0.018223702907562256, -0.006688273511826992, 0.002910637529566884, -0.014327231794595718, 0.01675081066787243, -0.008690068498253822, 0.00017982265853788704, 0.015304697677493095, 0.022883402183651924, 0.010785593651235104, -0.026043426245450974, 0.00800718180835247, -0.01585368439555168, 0.014902999624609947, -0.043222714215517044, 0.0021859072148799896, -0.014956559054553509, -0.010075926780700684, 0.00988846831023693, 0.011354666203260422, 0.0017440392402932048, -0.028627684339880943, -0.011100257746875286, 0.0005703276256099343, -0.018022853881120682, -0.01991083472967148, 0.02108914963901043, 0.010102706961333752, 0.0129212886095047, 0.016724031418561935, 0.031653810292482376, 0.04469560831785202, -0.004569315817207098, -0.034974515438079834, -0.010691864416003227, 0.032644666731357574, 0.01426028273999691, 0.006035513710230589, 0.022146955132484436, -0.025909526273608208, -0.021745257079601288, 0.007538534235209227, 0.007264040410518646, -0.010879323817789555, -0.011662635020911694, -0.017634546384215355, 0.03446569666266441, 0.014434351585805416, -0.043999332934617996, -0.04900716617703438, -0.006581153720617294, 0.022321024909615517, 0.02967209927737713, 4.885234739049338e-05, 0.015237747691571712, 0.00642382213845849, 0.017031999304890633, -0.018143363296985626, 0.005255550146102905, 0.0036186303477734327, -0.027476150542497635, -0.0171658992767334, -0.007317600306123495, 0.020285753533244133, -0.0022495093289762735, 0.013242647051811218, 0.0020151855424046516, -0.024543752893805504, 0.04887326806783676, -0.011803229339420795, -0.01333637721836567, 0.02951142005622387, -0.02427595481276512, 0.011267631314694881, 0.030154136940836906, -0.02335204929113388, 0.023539507761597633, 0.011776449158787727, -0.006330092437565327, 0.01818353310227394, -0.0032654707320034504, -0.0096675343811512, -0.014782490208745003, -0.0071502262726426125, -0.01908065937459469, -0.026873603463172913, -0.015184188261628151, 0.01985727623105049, -0.024128666147589684, 0.0037224022671580315, 0.009901857934892178, -0.0028855314012616873, -0.023726968094706535, -0.01634911261498928, -0.007136836182326078, -0.008221421390771866, 0.017781835049390793, 0.0007711766520515084, -0.0131690027192235, -0.023860866203904152, 0.00754522904753685, -0.01251289527863264, -0.015117238275706768, 0.028038527816534042, 0.013229257427155972, 0.004251305013895035, 0.0005017041694372892, -0.008817273192107677, -0.00746488943696022, -0.02210678532719612, -0.023619847372174263, -0.01735335774719715, 0.003104791510850191, 0.010772204026579857, -0.00021361133258324116, -0.005469789262861013, 0.0005682354094460607, -0.000828920747153461, 0.01958947628736496, 0.001572480658069253, 0.011394836008548737, -0.012198232114315033, 0.007270735688507557, -0.028654463589191437, -0.025333760306239128, -0.022387973964214325, -0.019562697038054466, 0.01660352200269699, -0.0032186058815568686, -0.025547998026013374, -0.017125729471445084, 0.0023281751200556755, -0.004867241717875004, 0.0008812252199277282, 0.035885028541088104, 0.004227872472256422, -0.0006874895771034062, 0.009111851453781128, -0.029966678470373154, -0.00467308796942234, 0.011227461509406567, 0.012794083915650845, -0.020312532782554626, -0.0034211287274956703, -0.0011515344958752394, 0.007987096905708313, -0.012539675459265709, -0.0036956225521862507, 0.014876219443976879, -0.007598788943141699, -0.01692488044500351, -0.07316261529922485, 0.014916389249265194, 0.002221055794507265, -0.020205413922667503, -0.004740037489682436, -0.013523835688829422, -0.002600995125249028, 0.0021490848157554865, -0.02027236297726631, 0.028949042782187462, -0.012981543317437172, -0.01338993664830923, 0.014782490208745003, -0.004509061109274626, -0.016067923977971077, -0.017741665244102478, 0.0020971987396478653, -0.008228115737438202, 0.009165411815047264, 0.024168835952878, 0.01300832349807024, -0.0004033718432765454, -0.01859862171113491, 0.0075920941308140755, -0.011796534061431885, 0.014876219443976879, -0.029832778498530388, 0.02234780415892601, -0.010109402239322662, 0.0027281995862722397, 0.0005661432514898479, -0.03982166945934296, -0.007645653560757637, -0.030395155772566795, -0.008301761001348495, -0.01205094251781702, 0.032242968678474426, 0.03269822522997856, 0.014996728859841824, 0.06282558292150497, -0.016483012586832047, -0.028118867427110672, 0.011388140730559826, 0.002477138303220272, -0.019897446036338806, 0.03034159541130066, -0.01584029570221901, -0.0038228267803788185, 0.040303707122802734, -0.005165168084204197, 0.022401364520192146, 0.0005548454937525094, -0.00610581086948514, -0.0006950214155949652, 0.011722889728844166, -0.024704432114958763, 0.049998022615909576, 0.0014979991829022765, 0.0023030689917504787, -0.013309597037732601, 0.013671125285327435, -0.001006755861453712, -0.0008088358445093036, -0.016389282420277596, 0.0083352355286479, 0.016643691807985306, -0.015465376898646355, -0.013095357455313206, 0.021531017497181892, -0.00763226393610239, -0.023204760625958443, 0.002833645325154066, 0.010705254040658474, 0.03591180965304375, -0.022039836272597313, 0.016027754172682762, 0.009908553212881088, 0.0013122138334438205, -0.013102052733302116, 0.013805024325847626, 0.0005983627634122968, -0.001440255087800324, -0.009533634409308434, 0.00887752790004015, 0.014434351585805416, 0.03727758303284645, -0.01300162822008133, 0.015291307121515274, 0.0003562978527043015, 0.01004245225340128, 0.011153817176818848, 0.012519590556621552, -0.0023901036474853754, 0.009085072204470634, -0.012238401919603348, 0.01174966897815466, -0.007076581474393606, 0.009011426940560341, 0.012606625445187092, 0.021946106106042862, 0.038911156356334686, -0.008120996877551079, -0.004304864443838596, -0.040062688291072845, -0.02686021290719509, 0.014836049638688564, -0.02568189799785614, -0.02517308108508587, 0.016067923977971077, -0.01692488044500351, -0.011247546412050724, -0.0033642216585576534, 0.002555804094299674, 0.02884192392230034, -0.022642383351922035, 0.01004245225340128, 0.014126382768154144, -0.015077068470418453, -0.022950351238250732, 0.05586281418800354, 0.0010008977260440588, 0.019964395090937614, 0.023633237928152084, -0.0021122624166309834, 0.017058778554201126, 0.011548819951713085, -0.010644999332726002, -0.004000243730843067, 0.01750064641237259, 0.014688760042190552, -0.004525798372924328, -0.008757018484175205, -0.013738075271248817, -0.015652835369110107, -0.009473379701375961, 0.013691210187971592, -0.024744601920247078, 0.0487125888466835, 0.005248855333775282, 0.03141279146075249, 0.005603688303381205, -0.011876873672008514, 0.007451499812304974, -0.008080827072262764, -0.0009439905406907201, 0.012767304666340351, -0.004425373859703541, -0.023070860654115677, 0.006239710375666618, 0.003375937696546316, -0.021531017497181892, -0.0010544575052335858, -0.023298488929867744, -0.0465434193611145, -0.0069828517735004425, 0.005335889756679535, 0.010845848359167576, -0.022870011627674103, 0.02466426230967045, 0.03267144411802292, 0.007940232753753662, 0.011789838783442974, 0.021664917469024658, -0.027743948623538017, 0.00571415526792407, 0.025387318804860115, -0.006433864589780569, -0.008482525125145912, -0.017527427524328232, 0.008810577914118767, -0.0060120816342532635, -0.02935074083507061, -0.029136501252651215, -0.0012871075887233019, -0.0030160832684487104, -0.0057576727122068405, -0.012010772712528706, 0.009306006133556366, 0.01525113731622696, 0.008187945932149887, 0.02927040122449398, -0.025909526273608208, -0.006296617444604635, 0.02134355902671814, 0.0029056163039058447, -0.000712595705408603, 0.0013063556980341673, -0.001610976760275662]\n"
     ]
    }
   ],
   "execution_count": 30
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 使用新方法调用 OpenAI Embedding API\n",
    "def embedding_text(text, model=\"text-embedding-ada-002\"):\n",
    "    res = client.embeddings.create(input=text, model=model)\n",
    "    return res.data[0].embedding"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "\n",
    "### 注意：如果未使用信用卡支付过 OpenAI 账单的同学，可以直接跳过此步骤。\n",
    "\n",
    "### 提醒：非必须步骤，可直接复用项目中的嵌入文件 fine_food_reviews_with_embeddings_1k\n",
    "\n",
    "对于免费试用用户的前48小时，OpenAI 设置了 [速率限制](https://platform.openai.com/docs/guides/rate-limits/overview)\n",
    "\n",
    "如果你已经支付过 OpenAI API 账单，可以尝试取消注释，调用以下代码测试批量 Embedding："
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 实际生成会耗时几分钟，逐行调用 OpenAI Embedding API\n",
    "\n",
    "# df[\"embedding\"] = df.combined.apply(embedding_text)\n",
    "# output_datapath = \"data/fine_food_reviews_with_embeddings_1k_1126.csv\"\n",
    "# df.to_csv(output_datapath)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# e0 = df[\"embedding\"][0]"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {
    "scrolled": true
   },
   "source": [
    "# e0"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 2.读取 fine_food_reviews_with_embeddings_1k 嵌入文件"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "embedding_datapath = \"data/fine_food_reviews_with_embeddings_1k.csv\"\n",
    "\n",
    "df_embedded = pd.read_csv(embedding_datapath, index_col=0)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "attachments": {},
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "#### 查看 Embedding 结果"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "df_embedded[\"embedding\"]"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "len(df_embedded[\"embedding\"][0])"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "type(df_embedded[\"embedding\"][0])"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {
    "collapsed": true,
    "jupyter": {
     "outputs_hidden": true
    },
    "scrolled": true
   },
   "source": [
    "df_embedded[\"embedding\"][0]"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "import ast\n",
    "\n",
    "# 将字符串转换为向量\n",
    "df_embedded[\"embedding_vec\"] = df_embedded[\"embedding\"].apply(ast.literal_eval)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "len(df_embedded[\"embedding_vec\"][0])"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "df_embedded.head(2)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 3. 使用 t-SNE 可视化 1536 维 Embedding 美食评论"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 导入 NumPy 包，NumPy 是 Python 的一个开源数值计算扩展。这种工具可用来存储和处理大型矩阵，\n",
    "# 比 Python 自身的嵌套列表（nested list structure)结构要高效的多。\n",
    "import numpy as np\n",
    "# 从 matplotlib 包中导入 pyplot 子库，并将其别名设置为 plt。\n",
    "# matplotlib 是一个 Python 的 2D 绘图库，pyplot 是其子库，提供了一种类似 MATLAB 的绘图框架。\n",
    "import matplotlib.pyplot as plt\n",
    "import matplotlib\n",
    "\n",
    "# 从 sklearn.manifold 模块中导入 TSNE 类。\n",
    "# TSNE (t-Distributed Stochastic Neighbor Embedding) 是一种用于数据可视化的降维方法，尤其擅长处理高维数据的可视化。\n",
    "# 它可以将高维度的数据映射到 2D 或 3D 的空间中，以便我们可以直观地观察和理解数据的结构。\n",
    "from sklearn.manifold import TSNE"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "type(df_embedded[\"embedding_vec\"])"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 首先，确保你的嵌入向量都是等长的\n",
    "assert df_embedded['embedding_vec'].apply(len).nunique() == 1"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 将嵌入向量列表转换为二维 numpy 数组\n",
    "matrix = np.vstack(df_embedded['embedding_vec'].values)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 创建一个 t-SNE 模型，t-SNE 是一种非线性降维方法，常用于高维数据的可视化。\n",
    "# n_components 表示降维后的维度（在这里是2D）\n",
    "# perplexity 可以被理解为近邻的数量\n",
    "# random_state 是随机数生成器的种子\n",
    "# init 设置初始化方式\n",
    "# learning_rate 是学习率。\n",
    "tsne = TSNE(n_components=2, perplexity=15, random_state=42, init='random', learning_rate=200)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 使用 t-SNE 对数据进行降维，得到每个数据点在新的2D空间中的坐标\n",
    "vis_dims = tsne.fit_transform(matrix)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 定义了五种不同的颜色，用于在可视化中表示不同的等级\n",
    "colors = [\"red\", \"darkorange\", \"gold\", \"turquoise\", \"darkgreen\"]"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 从降维后的坐标中分别获取所有数据点的横坐标和纵坐标\n",
    "x = [x for x,y in vis_dims]\n",
    "y = [y for x,y in vis_dims]\n",
    "\n",
    "# 根据数据点的评分（减1是因为评分是从1开始的，而颜色索引是从0开始的）获取对应的颜色索引\n",
    "color_indices = df_embedded.Score.values - 1\n",
    "\n",
    "# 确保你的数据点和颜色索引的数量匹配\n",
    "assert len(vis_dims) == len(df_embedded.Score.values)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 创建一个基于预定义颜色的颜色映射对象\n",
    "colormap = matplotlib.colors.ListedColormap(colors)\n",
    "# 使用 matplotlib 创建散点图，其中颜色由颜色映射对象和颜色索引共同决定，alpha 是点的透明度\n",
    "plt.scatter(x, y, c=color_indices, cmap=colormap, alpha=0.3)\n",
    "\n",
    "# 为图形添加标题\n",
    "plt.title(\"Amazon ratings visualized in language using t-SNE\")"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "**t-SNE降维后，评论大致分为3个大类。**"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 4. 使用 K-Means 聚类，然后使用 t-SNE 可视化"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "import numpy as np\n",
    "# 从 scikit-learn中导入 KMeans 类。KMeans 是一个实现 K-Means 聚类算法的类。\n",
    "from sklearn.cluster import KMeans\n",
    "\n",
    "# np.vstack 是一个将输入数据堆叠到一个数组的函数（在垂直方向）。\n",
    "# 这里它用于将所有的 ada_embedding 值堆叠成一个矩阵。\n",
    "# matrix = np.vstack(df.ada_embedding.values)\n",
    "\n",
    "# 定义要生成的聚类数。\n",
    "n_clusters = 4\n",
    "\n",
    "# 创建一个 KMeans 对象，用于进行 K-Means 聚类。\n",
    "# n_clusters 参数指定了要创建的聚类的数量；\n",
    "# init 参数指定了初始化方法（在这种情况下是 'k-means++'）；\n",
    "# random_state 参数为随机数生成器设定了种子值，用于生成初始聚类中心。\n",
    "# n_init=10 消除警告 'FutureWarning: The default value of `n_init` will change from 10 to 'auto' in 1.4'\n",
    "kmeans = KMeans(n_clusters = n_clusters, init='k-means++', random_state=42, n_init=10)\n",
    "\n",
    "# 使用 matrix（我们之前创建的矩阵）来训练 KMeans 模型。这将执行 K-Means 聚类算法。\n",
    "kmeans.fit(matrix)\n",
    "\n",
    "# kmeans.labels_ 属性包含每个输入数据点所属的聚类的索引。\n",
    "# 这里，我们创建一个新的 'Cluster' 列，在这个列中，每个数据点都被赋予其所属的聚类的标签。\n",
    "df_embedded['Cluster'] = kmeans.labels_"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "df_embedded['Cluster']"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "df_embedded.head(2)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 首先为每个聚类定义一个颜色。\n",
    "colors = [\"red\", \"green\", \"blue\", \"purple\"]\n",
    "\n",
    "# 然后，你可以使用 t-SNE 来降维数据。这里，我们只考虑 'embedding_vec' 列。\n",
    "tsne_model = TSNE(n_components=2, random_state=42)\n",
    "vis_data = tsne_model.fit_transform(matrix)\n",
    "\n",
    "# 现在，你可以从降维后的数据中获取 x 和 y 坐标。\n",
    "x = vis_data[:, 0]\n",
    "y = vis_data[:, 1]\n",
    "\n",
    "# 'Cluster' 列中的值将被用作颜色索引。\n",
    "color_indices = df_embedded['Cluster'].values\n",
    "\n",
    "# 创建一个基于预定义颜色的颜色映射对象\n",
    "colormap = matplotlib.colors.ListedColormap(colors)\n",
    "\n",
    "# 使用 matplotlib 创建散点图，其中颜色由颜色映射对象和颜色索引共同决定\n",
    "plt.scatter(x, y, c=color_indices, cmap=colormap)\n",
    "\n",
    "# 为图形添加标题\n",
    "plt.title(\"Clustering visualized in 2D using t-SNE\")\n",
    "\n",
    "# 显示图形\n",
    "plt.show()"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "**K-MEANS 聚类可视化效果，4类（官方介绍：一个专注于狗粮，一个专注于负面评论，两个专注于正面评论）。**"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 5. 使用 Embedding 进行文本搜索"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "![cosine](images/cosine.png)"
   ]
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# cosine_similarity 函数计算两个嵌入向量之间的余弦相似度。\n",
    "def cosine_similarity(a, b):\n",
    "    return np.dot(a, b) / (np.linalg.norm(a) * np.linalg.norm(b))"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "type(df_embedded[\"embedding_vec\"][0])"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 定义一个名为 search_reviews 的函数，\n",
    "# Pandas DataFrame 产品描述，数量，以及一个 pprint 标志（默认值为 True）。\n",
    "def search_reviews(df, product_description, n=3, pprint=True):\n",
    "    product_embedding = embedding_text(product_description)\n",
    "    \n",
    "    df[\"similarity\"] = df.embedding_vec.apply(lambda x: cosine_similarity(x, product_embedding))\n",
    "\n",
    "    results = (\n",
    "        df.sort_values(\"similarity\", ascending=False)\n",
    "        .head(n)\n",
    "        .combined.str.replace(\"Title: \", \"\")\n",
    "        .str.replace(\"; Content:\", \": \")\n",
    "    )\n",
    "    if pprint:\n",
    "        for r in results:\n",
    "            print(r[:200])\n",
    "            print()\n",
    "    return results"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "# 使用 'delicious beans' 作为产品描述和 3 作为数量，\n",
    "# 调用 search_reviews 函数来查找与给定产品描述最相似的前3条评论。\n",
    "# 其结果被存储在 res 变量中。\n",
    "res = search_reviews(df_embedded, 'delicious beans', n=3)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "res = search_reviews(df_embedded, 'dog food', n=3)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "res = search_reviews(df_embedded, 'awful', n=5)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [
    "def search_reviews(df, product_description, n=3, pprint=True):\n",
    "    product_embedding = embedding_text(product_description)\n",
    "\n",
    "    df[\"similarity\"] = df.embedding_vec.apply(lambda x: cosine_similarity(x, product_embedding))\n",
    "\n",
    "    results = (\n",
    "        df.sort_values(\"similarity\", ascending=False)\n",
    "        .head(n)\n",
    "        .combined.str.replace(\"Title: \", \"\")\n",
    "        .str.replace(\"; Content:\", \": \")\n",
    "    )\n",
    "    if pprint:\n",
    "        for r in results:\n",
    "            print(r[:200])\n",
    "            print()\n",
    "    return results\n",
    "\n",
    "res = search_reviews(df_embedded, 'dog food', n=3)"
   ],
   "outputs": [],
   "execution_count": null
  },
  {
   "cell_type": "code",
   "metadata": {},
   "source": [],
   "outputs": [],
   "execution_count": null
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.10.14"
  },
  "vscode": {
   "interpreter": {
    "hash": "365536dcbde60510dc9073d6b991cd35db2d9bac356a11f5b64279a5e6708b97"
   }
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}
